/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package listcontrol;

import java.io.ByteArrayInputStream;
import java.io.DataInputStream;
import java.io.IOException;
import java.net.InetAddress;
import java.net.Socket;
import java.util.ArrayList;
import java.util.UUID;
import network.ListRequestListener;
import util.CompleteFile;
import util.PartDownload;

/**
 *
 * @author gravena
 */
public class RemoteFileList extends LocalFileList {
    private InetAddress ip;
    private boolean updated;
    private UUID uuid;
    private int connections;
    
    public RemoteFileList(InetAddress ip) {
        this.ip = ip;
        this.connections = 0;
    }
    
    @Override
    public void rebuildList() {
        // Nas listas remotas esse método não pode fazer nada
    }
    
    public static RemoteFileList searchPeer(ArrayList<RemoteFileList> peers, UUID uuid) {
        for(int i=0;i<peers.size();i++) {
            if(peers.get(i).getUUID().equals(uuid)) {
                return peers.get(i);
            }
        }
        return null;
    }

    public boolean isUpdated() {
        synchronized(this) {
            return updated;
        }
    }

    public void setUpdated(boolean updated) {
        synchronized(this) {
            this.updated = updated;
        }
    }
        
    
    public boolean getFileList() {
        Socket conn=null;
        DataInputStream input=null;
        try {
            conn = new Socket(ip, ListRequestListener.LIST_REQUEST_PORT);
            input = new DataInputStream(conn.getInputStream());
            byte header[] = new byte[44];
            
            PartDownload.transfer(input, header, header.length);             
            
            byte string[] = new byte[32];
            long version;
            int packetSize;
            
            ByteArrayInputStream bis = new ByteArrayInputStream(header);
            DataInputStream dis = new DataInputStream(bis);
                        
            PartDownload.transfer(dis, string, 32);            
            version = dis.readLong();
            packetSize = dis.readInt();
            
            int i = 0;
            this.resetList();
            while(i<packetSize) {
                byte[] md5 = new byte[16];                
                PartDownload.transfer(input, md5, 16);                
                long size = input.readLong();
                int nameSize = input.readInt();
                                
                byte[] name = new byte[nameSize];                
                PartDownload.transfer(input, name, nameSize);                
                String nameString = new String(name);                                                                       
                boolean complete = input.readBoolean();                
                                
                i += 1 + 16 + 8 + 4 + nameSize;
                
                if(!this.searchFile(md5)) {
                    CompleteFile newFile = new CompleteFile();
                    newFile.setHashMD5(md5);
                    newFile.setSize(size);
                    newFile.setName(nameString);
                    newFile.setComplete(complete);
                    this.addCompleteFile(newFile);                    
                }
            }
            
            this.setVersion(version);
            this.setUpdated(true);
            
            input.close();
            conn.close();
            
            return true;
        } catch (IOException ex) {
            if(conn != null) {
                System.err.println("[RFL] Não foi possível estabelecer conexão com " + conn.getInetAddress() + "!\n" + ex.getMessage());
            } else {
                System.err.println("[RFL]Erro na abertura do socket.\n" + ex.getMessage());
            }
            return false;
        }
                
    }
    
    @Override
    public void setUuid(UUID uuid) {
        this.uuid = uuid;
    }
    
    @Override
    public UUID getUUID() {
        return this.uuid;
    }
    
    @Override
    public String getUUIDString() {
        String u = this.uuid.toString();
        StringBuilder v = new StringBuilder(u.length());
        
        int i=0;
    
        while(i < u.length()) {
            if(u.charAt(i) != '-') {
                v.append(u.charAt(i));
            }
            i++;
        }
        
        return v.toString();
    }

    public InetAddress getIp() {
        return ip;
    }    
    
    public void setConnections(int connections) {
        this.connections = connections;
    }
    
    public int getConnections() {
        return this.connections;
    }
}
